package com.siwei.apply.service.impl;

import com.siwei.apply.domain.NodeAttachment;
import com.siwei.apply.mapper.NodeAttachmentMapper;
import com.siwei.apply.service.NodeAttachmentService;
import com.siwei.apply.utils.FileExtractUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.nio.file.*;
import java.util.*;

/**
 * 记录流程对应的附件材料 服务实现类
 */
@Service
public class NodeAttachmentImpl implements NodeAttachmentService {
    
    private static final Logger logger = LoggerFactory.getLogger(NodeAttachmentImpl.class);
    
    @Autowired
    private NodeAttachmentMapper nodeAttachmentMapper;

    /**
     * 根据ID查询附件信息
     * @param id 附件ID
     * @return
     */
    @Override
    public NodeAttachment getById(String id) {
        try {
            if (id == null || id.trim().isEmpty()) {
                logger.warn("查询附件信息失败：id不能为空");
                return null;
            }

            NodeAttachment nodeAttachment = nodeAttachmentMapper.selectById(id);
            logger.info("查询附件信息，id: {}", id);
            return nodeAttachment;

        } catch (Exception e) {
            logger.error("查询附件信息异常，id: {}", id, e);
            return null;
        }
    }

    /**
     * 根据节点ID查询附件信息
     * @param nodeId 节点ID
     * @return
     */
    @Override
    public NodeAttachment getByNodeId(String nodeId) {
        try {
            if (nodeId == null || nodeId.trim().isEmpty()) {
                logger.warn("查询附件信息失败：nodeId不能为空");
                return null;
            }

            NodeAttachment nodeAttachment = nodeAttachmentMapper.selectByNodeId(nodeId);
            logger.info("查询节点附件信息，nodeId: {}", nodeId);
            return nodeAttachment;

        } catch (Exception e) {
            logger.error("查询节点附件信息异常，nodeId: {}", nodeId, e);
            return null;
        }
    }

    /**
     * 处理文件并保存附件信息
     * @param filePath 文件路径
     * @return
     */
    @Override
    @Transactional(rollbackFor = Exception.class)
    public String processFileAndSave(String filePath) {
        try {
            if (filePath == null || filePath.trim().isEmpty()) {
                logger.warn("处理文件失败：filePath不能为空");
                return null;
            }

            Path file = Paths.get(filePath);
            if (!Files.exists(file)) {
                logger.warn("处理文件失败：文件不存在: {}", filePath);
                return null;
            }

            Map<String, Object> directoryStructure;

            // 判断是否为压缩文件
            if (FileExtractUtil.isCompressedFile(filePath)) {
                // 解压文件到同名文件夹并获取目录结构
                String extractDir = FileExtractUtil.extractToSameNameFolder(filePath);
                if (extractDir != null) {
                    directoryStructure = FileExtractUtil.getDirectoryStructure(Paths.get(extractDir));
                } else {
                    logger.error("解压文件失败: {}", filePath);
                    return null;
                }
            } else {
                // 直接获取文件信息
                directoryStructure = FileExtractUtil.getFileStructure(file);
            }

            // 保存附件信息并返回ID
            String id = saveAttachment(directoryStructure);

            logger.info("成功处理文件并保存附件信息，id: {}, filePath: {}", id, filePath);
            return id;

        } catch (Exception e) {
            logger.error("处理文件并保存附件信息异常，filePath: {}", filePath, e);
            return null;
        }
    }
    
    @Override
    public void deleteByNodeId(String nodeId) {
        try {
            if (nodeId == null || nodeId.trim().isEmpty()) {
                throw new IllegalArgumentException("nodeId不能为空");
            }

            nodeAttachmentMapper.deleteByNodeId(nodeId);
            logger.info("删除节点附件信息，nodeId: {}", nodeId);

        } catch (Exception e) {
            logger.error("删除节点附件信息异常，nodeId: {}", nodeId, e);
            throw e;
        }
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean updateNodeId(String nodeAttachmentId, String nodeId) {
        try {
            if (nodeAttachmentId == null || nodeAttachmentId.trim().isEmpty()) {
                logger.warn("更新nodeId失败：nodeAttachmentId不能为空");
                return false;
            }

            if (nodeId == null || nodeId.trim().isEmpty()) {
                logger.warn("更新nodeId失败：nodeId不能为空");
                return false;
            }

            // 先根据nodeId删除其他的附件记录
            nodeAttachmentMapper.deleteByNodeIdAndIdNotEqual(nodeId, nodeAttachmentId);
            logger.info("删除nodeId对应的其他附件记录，nodeId: {}", nodeId);

            // 再查询要更新的记录是否存在
            NodeAttachment existing = nodeAttachmentMapper.selectById(nodeAttachmentId);
            if (existing == null) {
                logger.warn("更新nodeId失败：附件记录不存在，nodeAttachmentId: {}", nodeAttachmentId);
                return false;
            }

            // 更新nodeId
            existing.setNodeId(nodeId);
            nodeAttachmentMapper.updateById(existing);

            logger.info("成功更新nodeId，nodeAttachmentId: {}, nodeId: {}", nodeAttachmentId, nodeId);
            return true;

        } catch (Exception e) {
            logger.error("更新nodeId异常，nodeAttachmentId: {}, nodeId: {}", nodeAttachmentId, nodeId, e);
            return false;
        }
    }
    

    
    /**
     * 保存附件信息
     */
    private String saveAttachment(Map<String, Object> directoryStructure) {
        // 创建新记录
        NodeAttachment nodeAttachment = new NodeAttachment();
        nodeAttachment.generateId();
        nodeAttachment.setNodeId(null); // 不设置nodeId
        nodeAttachment.setAttachment(directoryStructure);
        nodeAttachmentMapper.insert(nodeAttachment);

        return nodeAttachment.getId();
    }
}
